﻿// <author>Netmon Cipher Dev Team</author>
// <date>2009-07-16</date>
// <version>1.0</version>
// <summary>This contains the entry point Main function.</summary>

namespace SSLDecryptionExpert
{
    using System;

    /// <summary>
    /// SSL Decryption Class
    /// </summary>
    public partial class SSLDecryption
    {
        #region Process Client Hello Message

        /// <summary>
        /// Evaluates Client Hello Message
        /// </summary>
        /// <param name="value">Field Value</param>
        /// <param name="timeStamp">Time Satmp Value</param>
        /// <param name="currentState">Current State</param>
        /// <param name="nextfilterToSearch">Next Filter Value</param>
        /// <param name="filter">Filter Class Object</param>
        private void ProcessClientHello(
                                int[] value,
                                ref byte[] timeStamp,
                                ref CurrentState currentState,
                                ref string nextfilterToSearch,
                                NMFilters filter)
        {
            if (value.Length == 1)
            {
                timeStamp = BitConverter.GetBytes(value[0]);
                Array.Reverse(timeStamp);

                nextfilterToSearch = filter.ClientRandomBytesFilter;
                Buffer.BlockCopy(
                            timeStamp,
                            0,
                            Variables.clientRandomNumber,
                            0,
                            timeStamp.Length);
            }
            else
            {
                for (int i = timeStamp.Length; i < Variables.clientRandomNumber.Length; i++)
                {
                    Variables.clientRandomNumber[i] = (byte)value[i - timeStamp.Length];
                }

                currentState = CurrentState.ClientHelloDone;
            }
        }

        #endregion

        #region Process Server Hello Message

        /// <summary>
        /// Evaluates Server Hello Message
        /// </summary>
        /// <param name="value">Field Value</param>
        /// <param name="timeStamp">Time Satmp Value</param>
        /// <param name="currentState">Current State</param>
        /// <param name="nextfilterToSearch">Next Filter Value</param>
        /// <param name="filter">Filter Class Object</param>
        private void ProcessServerHello(
                            int[] value,
                            ref byte[] timeStamp,
                            ref CurrentState currentState,
                            ref string nextfilterToSearch,
                            NMFilters filter)
        {
            if (value.Length == 1)
            {
                timeStamp = BitConverter.GetBytes(value[0]);
                Array.Reverse(timeStamp);
                nextfilterToSearch = filter.ServerRandomBytesFilter;
                Buffer.BlockCopy(
                            timeStamp,
                            0,
                            Variables.serverRandomNumber,
                            0,
                            timeStamp.Length);
            }
            else
            {
                for (int i = timeStamp.Length; i < Variables.serverRandomNumber.Length; i++)
                {
                    Variables.serverRandomNumber[i] = (byte)value[i - timeStamp.Length];
                }

                currentState = CurrentState.ServerHelloDone;
            }
        }

        #endregion

        #region Process Client Key Exchange Message

        /// <summary>
        /// Evaluates Client Key Exchange
        /// </summary>
        /// <param name="value">Field value</param>
        /// <returns>Returns Encrypted Key Exchange Data</returns>
        private byte[] ProcessClientKeyExchange(int[] value)
        {
            byte[] keyExchangeData;

            if (value.Length / 8 == 16)
            {
                keyExchangeData = new byte[128];
            } 
            else if (value.Length / 8 == 8)
            {
                keyExchangeData = new byte[64];
            }
            else if (value.Length / 8 == 32)
            {
                keyExchangeData = new byte[256];
            }
            else if (value.Length / 8 == 64)
            {
                keyExchangeData = new byte[512];
            }
            else
            {
                Variables.Log.LogMessage("Unrecognized size, using 256. KeyExchangeData length is " + value.Length);
                keyExchangeData = new byte[256];
            }

            int startIndex = 0;
            if (keyExchangeData.Length != value.Length)
            {
                startIndex = value.Length - keyExchangeData.Length;
            }

            if (startIndex >= 0)
            {
                for (int i = startIndex; i < keyExchangeData.Length + startIndex; i++)
                {
                    keyExchangeData[i - startIndex] = (byte)value[i];
                }
            }

            return keyExchangeData;
        }

        #endregion        
    }
}